package com.ray.filter;
import static org.hamcrest.CoreMatchers.instanceOf;

import java.lang.reflect.Modifier;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;

import org.apache.ibatis.javassist.ClassClassPath;
import org.apache.ibatis.javassist.ClassPool;
import org.apache.ibatis.javassist.CtClass;
import org.apache.ibatis.javassist.CtMethod;
import org.apache.ibatis.javassist.bytecode.CodeAttribute;
import org.apache.ibatis.javassist.bytecode.LocalVariableAttribute;
import org.apache.ibatis.javassist.bytecode.MethodInfo;
import org.apache.log4j.Logger;
import org.aspectj.lang.JoinPoint;
import org.aspectj.lang.annotation.AfterReturning;
import org.aspectj.lang.annotation.AfterThrowing;
import org.aspectj.lang.annotation.Aspect;
import org.aspectj.lang.annotation.Before;
import org.aspectj.lang.annotation.Pointcut;
import org.springframework.stereotype.Component;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import com.ray.exception.ServiceException;
import com.ray.pojo.MyUser;
import com.ray.util.ExceptionUtil;
import com.ray.util.RequestUtil;
import com.ray.util.redis.RedisCache;

import redis.clients.jedis.Jedis;
import redis.clients.jedis.JedisPool;
/**
 * 请求拦截处理
 * @author Shensg
 * 2018年8月4日
 */
@Aspect
@Component
public class HttpAspect {
	private Logger logger = Logger.getLogger(HttpAspect.class);  
	  
    ThreadLocal<Long> startTime = new ThreadLocal<>();  
    ThreadLocal<String> classMethod = new ThreadLocal<>();  
  
    @Pointcut("execution(public * com.ray.controller.*.*(..))") 
    public void webLog(){}  
  
    @Before("webLog()")  
    public void doBefore(JoinPoint joinPoint) throws Throwable {  
        startTime.set(System.currentTimeMillis());  
        // 接收到请求，记录请求内容  
        ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();  
        HttpServletRequest request = attributes.getRequest();  
        MyUser user=(MyUser)request.getSession().getAttribute("userLogin");
        if(user!=null) {
        	 // 记录下请求内容  
        	String info = "公司="+user.getCompany()+"\r\n"
    		+"用户名="+user.getUserName()+"\r\n"
    		+"URL=" + request.getRequestURL().toString()+"\r\n"
    		+"HTTP_METHOD=" + request.getMethod()+"\r\n"
    		+"IP=" + request.getRemoteAddr()+"\r\n"
    		+"CLASS_METHOD=" + joinPoint.getSignature().getDeclaringTypeName() + "." + joinPoint.getSignature().getName();
            classMethod.set(info);
            logger.info(info+"[入参={"+RequestUtil.getRequestAllParam(request)+"}]");  
        }
    }  
  
    @AfterReturning(returning = "ret", pointcut = "webLog()")  
    public void doAfterReturning(Object ret) throws Throwable {  
        // 处理完请求，返回内容  
        logger.info(((classMethod.get()!=null)?classMethod.get():"")+"[出参={"+ret+"}]");  
    	if((System.currentTimeMillis() - startTime.get())>500) {
    		logger.error(((classMethod.get()!=null)?classMethod.get():"")+"耗时=" + (System.currentTimeMillis() - startTime.get()));
    		return;
    	}
        logger.info(((classMethod.get()!=null)?classMethod.get():"")+"耗时=" + (System.currentTimeMillis() - startTime.get()));  
    }  
    
    @AfterThrowing(pointcut = "webLog()", throwing = "e")
	private void exception(JoinPoint joinPoint,  Throwable e) {
    	// 接收到请求，记录请求内容  
        ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();  
        HttpServletRequest request = attributes.getRequest();  
        // 域名
        String tempContextUrl = request.getHeader("Host");
        JSONObject json = new JSONObject();
    	JedisPool jedisPool = null;
    	Jedis jedis = null;
    	try {
    		//业务异常
        	if(e instanceof ServiceException) {
        		json.put("errType", "ServiceException");
        	}else {
        		json.put("errType", "Exception");
        	}
        	//错误信息
        	json.put("errTips", e.getMessage());
        	json.put("errMsgInfo", ExceptionUtil.getStackTrace(e));
        	//错误发生位置
        	json.put("location", (classMethod.get()!=null)?classMethod.get():"");
        	jedisPool = RedisCache.getPool();
        	//非业务异常
        	jedis = jedisPool.getResource();
        	System.out.println(tempContextUrl);
        	jedis.lpush("systemlog-list-"+tempContextUrl,json.toJSONString());
		} catch (Exception e2) {
			// TODO: handle exception
			logger.error("HttpAspect:"+ ExceptionUtil.getStackTrace(e2));
		}finally {
			RedisCache.returnResource(jedisPool, jedis);
		}
    	
	}
}
